package com.cskaoyan.configuration.shiro;

import com.cskaoyan.domain.MarketUser;
import com.cskaoyan.domain.MarketUserExample;
import com.cskaoyan.mapper.MarketUserMapper;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.Arrays;
import java.util.List;

/**
 * 提供自定义的Realm → 查询信息
 * @author stone
 * @date 2023/06/16 11:18
 */
@Component
public class MarketRealm extends AuthorizingRealm {

    @Autowired
    MarketUserMapper userMapper;

    /**
     * 查询认证信息 → 认证器会用
     */
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        UsernamePasswordToken token = (UsernamePasswordToken) authenticationToken;
        // 根据subject.login方法传入的AuthenticationToken获得用户名
        String username = token.getUsername();

        // 根据username做查询
        MarketUserExample example = new MarketUserExample();
        example.createCriteria().andUsernameEqualTo(username);
        List<MarketUser> marketUsers = userMapper.selectByExample(example);

        if (marketUsers != null && marketUsers.size() == 1) {
            //Object principal  → 用户信息 需要subject帮你保管的用户信息 → 通过subject能够取出它
            //                    比如保存userId，比如保存user对象
            MarketUser user = marketUsers.get(0);

            //Object credentials  → 凭证 访问这个系统需要的凭证
            //                    认证会比较token里的password和你这里提供的credentials的值是否一致
            //                             token里的password应该是登录的时候传入的值
            //                             credentials应该是你应用提供的
            String credentials = user.getPassword();
            //String realmName → 没啥用
            return new SimpleAuthenticationInfo(user,credentials,this.getName());
        }
        return null;


    }

    /**
     * 查询授权信息 → 授权器会用
     * 查询当前用户所拥有的权限
     *     比如 你查询到当前用户的权限有  user:list 、cart:list、order:list
     *                                subject.isPermitted("user:list"):true
     *                                subject.isPermitted("cart:list"):true
     *                                subject.isPermitted("order:list"):true
     */
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        // 前面认证的时候保存在Subject的principal信息
        MarketUser principal = (MarketUser) principalCollection.getPrimaryPrincipal();
        // 查询当前这个marketUser的权限信息
        // 假如 查询到的权限信息有：user:list 、cart:list、order:list
        SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();
        List<String> permissions = Arrays.asList("user:list", "cart:list", "order:list");// 应该是查询数据库获得
        authorizationInfo.addStringPermissions(permissions);
        return authorizationInfo;
    }
}
